package com.vanke.devops.domain.domain.docker.impl;

import com.google.common.collect.Lists;
import com.vanke.core.util.StringUtil;
import com.vanke.devops.domain.domain.docker.DockerService;
import com.vanke.devops.domain.domain.docker.dto.ServiceDTO;
import com.vanke.devops.domain.domain.docker.dto.TaskDTO;
import com.vanke.devops.domain.manager.docker.DockerManager;
import com.vanke.devops.domain.manager.docker.extend.enums.ServiceModel;
import com.vanke.devops.domain.manager.docker.extend.model.Node;
import com.vanke.devops.domain.manager.docker.extend.model.Task;
import org.joda.time.DateTime;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @author 陈景阳
 * @since 2018/6/7
 */
@Service
public class DockerServiceImpl implements DockerService {

    @Autowired
    private DockerManager dockerManager;

    @Override
    public List<ServiceDTO> services(String ip,String keyword) {
        if(StringUtil.isEmpty(ip)){
            return Lists.newArrayList();
        }
        List<com.vanke.devops.domain.manager.docker.extend.model.Service> list = dockerManager.services(ip);
        List<ServiceDTO> result = list.stream().map(this::getServiceDTO).collect(Collectors.toList());
        //模糊查询
        return result.stream()
                .filter(item -> item.getName().contains(keyword))
                .collect(Collectors.toList());
    }

    @Override
    public ServiceDTO getServiceById(String ip, String id) {
        com.vanke.devops.domain.manager.docker.extend.model.Service service = dockerManager.service(ip,id);
        return this.getServiceDTO(service);
    }

    @Override
    public List<TaskDTO> getTasksByServiceName(String ip, String serviceName) {
        List<Task> tasks = dockerManager.withServiceNameTasks(ip,serviceName);
        List<Node> nodes = dockerManager.nodes(ip);
        Map<String,Node> nodeIpMap = nodes.stream()
                .collect(Collectors.toMap(
                        Node::getId,
                        node -> node));

        return tasks.stream().map(task -> {
            TaskDTO dto = new TaskDTO();
            dto.setId(task.getId());
            dto.setStatus(task.getStatus().getState());
            dto.setLastUpdate(new DateTime(task.getUpdatedAt()).toDate());
            dto.setNode(nodeIpMap.get(task.getNodeID()).getDescription().getHostname());
            dto.setNodeIp(nodeIpMap.get(task.getNodeID()).getStatus().getAddr());
            return dto;
        }).collect(Collectors.toList());
    }

    private ServiceDTO getServiceDTO(com.vanke.devops.domain.manager.docker.extend.model.Service service){
        ServiceDTO dto = new ServiceDTO();
        dto.setId(service.getId());
        dto.setName(service.getSpec().getName());
        dto.setImage(service.getSpec().getTaskTemplate().getContainerSpec().getImage());
        dto.setCreated(new DateTime(service.getCreateAt()).toDate());
        dto.setLastUpdate(new DateTime(service.getUpdatedAt()).toDate());
        dto.setReplicas(service.getSpec().getMode().getReplicated().getReplicas());
        dto.setVersion(service.getVersion().getIndex());
        if(service.getSpec().getMode().getReplicated() != null){
            dto.setSchedulingMode(ServiceModel.REPLICATED.getValue());
        }
        List<ServiceDTO.Port> ports= service.getEndpoint()
                .getPorts()
                .stream()
                .map(item -> {
                    ServiceDTO.Port port =dto.new Port();
                    port.setPublishPort(item.getPublishedPort());
                    port.setTargetPort(item.getTargetPort());
                    return port;
                }).collect(Collectors.toList());
        dto.setPorts(ports);
        return dto;
    }

}
